package org.yray.io.controller;

import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.servlet.mvc.method.annotation.SseEmitter;

import java.io.IOException;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.ConcurrentHashMap;

@Controller
@Slf4j
public class SseControllerTest {

    private static final Map<String, SseEmitter> sseEmitterMap=new ConcurrentHashMap<>();
    @GetMapping("/sse/connect")
    public SseEmitter connect(@RequestParam("uid")String uid)
    {
        log.info("come={}",uid);
        SseEmitter sseEmitter= sseEmitterMap.get(uid);
        if(sseEmitter==null)
        {
            sseEmitter= new SseEmitter(0L);
            sseEmitterMap.put(uid,sseEmitter);
        }

        Thread thread=new Thread(new SseEmitterRunnable(sseEmitter,uid));
        thread.setName("SSE-"+uid+"-"+ UUID.randomUUID().toString().replaceAll("-",""));
        thread.start();

        return sseEmitter;
    }
    public static class SseEmitterRunnable implements Runnable{

        private SseEmitter sseEmitter;
        private String uid;
        public SseEmitterRunnable(SseEmitter sseEmitter,String uid)
        {
            this.sseEmitter=sseEmitter;
            this.uid=uid;
        }
        @Override
        public void run() {
            for(int i=0;i<3;i++) {
                try {
                    sseEmitter.send("uid="+uid+",notice="+i);
                    Thread.sleep(2000);
                } catch (Exception e) {
                    log.error("thread={},uid={},notice={},err=",Thread.currentThread().getName(),uid,i,e);
                }

            }
            for(Map.Entry<String,SseEmitter> entry:sseEmitterMap.entrySet())
            {
                try {
                    entry.getValue().send("uid="+entry.getKey()+",tip");
                } catch (Exception e) {
                    log.error("thread={},uid={},tip,err=",Thread.currentThread().getName(),entry.getKey(),e);
                }
            }
        }
    }
    @GetMapping("/stream")
    public SseEmitter stream(@RequestParam("uid") String uid) {
        log.info("hello sse,uid={}",uid);
        SseEmitter emitter = new SseEmitter(5 * 60 * 1000L);
        // 可以设置超时时间
        emitter.complete();

        // 发送消息
        try {
            Thread thread=new Thread(()->{
                for(int i=0;i<100;i++) {
                    try {
                        Thread.sleep(1000);
                        emitter.send(SseEmitter.event().data(uid+"-"+"Hello from server!"+i));
                        log.info("send succ,uid={},i={}",uid,i);
                    } catch (Exception e) {
                        log.error("uid={},i={},err=",uid,i,e);
                        e.printStackTrace();
                    }

                }
            });
            thread.start();
            log.info("return");
        } catch (Exception e) {

            e.printStackTrace();
        }
        //log.info("SseEmitter={}",RamUsageEstimator.humanSizeOf(emitter));
        return emitter;
    }

}
